package com.wutianyi.utils;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.HashMap;
import java.util.Map;

import org.apache.commons.lang.StringUtils;
import org.codehaus.jackson.map.ObjectMapper;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;

import com.google.appengine.api.datastore.Text;
import com.google.common.base.Optional;

/**
 * @author hanjiewu
 * 
 */
public class Utils {
	
	public static byte[] EMPTY_BYTES = new byte[0];
	
	public static final int DEFAULT_PAGE_SIZE = 20;
	
	private static ObjectMapper objectMapper = new ObjectMapper();
	private static final Map<String, String> parameters;
	
	static {
		parameters = new HashMap<String, String>();
		parameters.put("charset", "UTF-8");
	}
	
	/**
	 * 将unicode转化为字符串
	 * 
	 * @param dataStr
	 * @return
	 */
	// public static String decodeUnicode(String dataStr) {
	// int start = 0;
	// int end = 0;
	// StringBuffer buffer = new StringBuffer();
	// while (start > -1) {
	// end = dataStr.indexOf("\\u", start + 2);
	// String charStr = "";
	// if (end == -1) {
	// charStr = dataStr.substring(start + 2, dataStr.length());
	// } else {
	// charStr = dataStr.substring(start + 2, end);
	// }
	// char letter = (char) Integer.parseInt(charStr, 16);
	// buffer.append(letter);
	// start = end;
	// }
	// return buffer.toString();
	// }
	
	public static String decodeUnicode(String dataStr) {
		boolean isslash = false;
		int len = dataStr.length();
		String charStr = "";
		StringBuilder sb = new StringBuilder();
		for (int i = 0; i < len; i++) {
			char c = dataStr.charAt(i);
			switch (c) {
				case '\\':
					isslash = true;
					break;
				case 'u':
					if (isslash) {
						if (i + 4 < len) {
							charStr = dataStr.substring(i + 1, i + 5);
							sb.append((char) Integer.parseInt(charStr, 16));
							i = i + 4;
						} else {
							sb.append(dataStr.substring(i));
							i = len;
						}
					} else {
						sb.append(c);
					}
					isslash = false;
					break;
				default:
					if (isslash) {
						sb.append('\\');
					}
					sb.append(c);
					isslash = false;
			}
			
		}
		
		return sb.toString();
	}
	
	/**
	 * @param value
	 * @return
	 */
	public static String toHexString(String value) {
		StringBuilder sb = new StringBuilder();
		for (int i = 0; i < value.length(); i++) {
			sb.append('%');
			sb.append(Integer.toHexString(value.charAt(i)));
		}
		return sb.toString();
	}
	
	public static String encodeUnicode(String value) {
		StringBuilder sb = new StringBuilder();
		for (int i = 0; i < value.length(); i++) {
			char c = value.charAt(i);
			if (c >= 0 && c <= 127) {
				sb.append(c);
			} else {
				sb.append('\\');
				sb.append('u');
				sb.append(Integer.toHexString(value.charAt(i)).toUpperCase());
			}
			
		}
		return sb.toString();
	}
	
	public static int convertInt(Object obj, int defaultValue) {
		if (null == obj) {
			return defaultValue;
		}
		try {
			return Integer.parseInt(obj.toString());
		} catch (Exception e) {
			return defaultValue;
		}
	}
	
	public static Object unSerialize(Object bytes) {
		try {
			String value = null;
			if (bytes instanceof Text) {
				value = ((Text) bytes).getValue();
			} else {
				value = bytes.toString();
			}
			ByteArrayInputStream bis = new ByteArrayInputStream(value.getBytes("ISO-8859-1"));
			ObjectInputStream ois = new ObjectInputStream(bis);
			Object obj = ois.readObject();
			return obj;
		} catch (Exception e) {

		}
		return null;
	}
	
	public static String serialize(Object obj) {
		if (null == obj) {
			return StringUtils.EMPTY;
		}
		ByteArrayOutputStream baos = new ByteArrayOutputStream();
		ObjectOutputStream oos;
		try {
			oos = new ObjectOutputStream(baos);
			oos.writeObject(obj);
			return new String(baos.toByteArray(), "ISO-8859-1");
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		return StringUtils.EMPTY;
	}
	
	public static String stringToString(String value) {
		return Optional.fromNullable(value).or(StringUtils.EMPTY);
	}
	
	/**
	 * @param total
	 * @param pageNo
	 * @param pageSize
	 * @return
	 */
	public static int getPosition(int total, int pageNo, int pageSize) {
		if (pageNo <= 0) {
			pageNo = 1;
		}
		if (pageSize <= 0) {
			pageSize = DEFAULT_PAGE_SIZE;
		}
		int totalNo = total % pageSize == 0 ? total / pageSize : total / pageSize + 1;
		if (pageNo > totalNo) {
			pageNo = totalNo;
		}
		return (pageNo - 1) * pageSize;
	}
	
	public static ResponseEntity<String> createJsonResponse(int result, String msg, Object info) {
		String response = createJsonResult(result, msg, info);
		HttpHeaders headers = new HttpHeaders();
		headers.setContentType(new MediaType(MediaType.APPLICATION_JSON, parameters));
		
		return new ResponseEntity<String>(response, headers, HttpStatus.OK);
	}
	
	public static String createJsonResult(int result, String msg, Object info) {
		Map<String, Object> results = new HashMap<String, Object>();
		results.put("r", result);
		results.put("msg", msg);
		if (null != info) {
			results.put("info", info);
		}
		try {
			return objectMapper.writeValueAsString(results);
		} catch (Exception e) {

		}
		return "";
	}
	
	public static void main(String[] args) {
		System.out
				.println(decodeUnicode("afapjmpmpa['d\r\na\u51FA\u73B0\u5728\u7B2C\u4E8C\u4E2A\u6846\u4E2Dasdfa"));
	}
}
